package manager

import (
	"context"
	"errors"
	"github.com/stretchr/testify/mock"
	"gitverse.ru/synapse/kubelatte/pkg/api/v1alpha1"
	"gitverse.ru/synapse/kubelatte/pkg/logs"
	"gitverse.ru/synapse/kubelatte/pkg/operator/controllers"
	"gitverse.ru/synapse/kubelatte/pkg/operator/controllers/clientset/mocks"
	"go.uber.org/zap"
	"testing"
	"time"
)

func TestInitManager_Start(t *testing.T) {
	logs.Logger = zap.NewNop()
	controllers.KbltMutator = "true"
	defer func() { controllers.KbltMutator = "false" }()

	t.Parallel()
	t.Run("All_resources_got_test", func(t *testing.T) {
		clMock := mocks.NewV1Alpha1Interface(t)

		scopeMock := mocks.NewScopeInterface(t)
		triggerMock := mocks.NewTriggerInterface(t)
		templateMock := mocks.NewTemplateInterface(t)

		clMock.On("Scope", mock.Anything).Return(scopeMock).Maybe()
		clMock.On("Trigger", mock.Anything).Return(triggerMock).Maybe()
		clMock.On("Template", mock.Anything).Return(templateMock).Maybe()

		scopeMock.On("List", mock.Anything, mock.Anything).Return(&v1alpha1.ScopeList{Items: []v1alpha1.Scope{{}}}, nil).Maybe()
		triggerMock.On("List", mock.Anything, mock.Anything).Return(&v1alpha1.TriggerList{Items: []v1alpha1.Trigger{{}}}, nil).Maybe()
		templateMock.On("List", mock.Anything, mock.Anything).Return(&v1alpha1.TemplateList{Items: []v1alpha1.Template{{}}}, nil).Maybe()

		controllers.Cl = clMock

		m := GetInitManager()
		if m.DoesTriggersExist() || m.DoesScopesExist() || m.DoesTemplatesExist() {
			t.Fatal("Wrong manager initialization")
		}

		ctx, cancel := context.WithCancel(context.Background())
		go func() {
			time.Sleep(4 * time.Second)
			cancel()
		}()

		m.Start(ctx)
	})

	t.Run("context_exit", func(t *testing.T) {
		clMock := mocks.NewV1Alpha1Interface(t)

		scopeMock := mocks.NewScopeInterface(t)
		triggerMock := mocks.NewTriggerInterface(t)
		templateMock := mocks.NewTemplateInterface(t)

		clMock.On("Scope", mock.Anything).Return(scopeMock).Maybe()
		clMock.On("Trigger", mock.Anything).Return(triggerMock).Maybe()
		clMock.On("Template", mock.Anything).Return(templateMock).Maybe()

		scopeMock.On("List", mock.Anything, mock.Anything).Return(&v1alpha1.ScopeList{Items: []v1alpha1.Scope{{}}}, errors.New("")).Maybe()
		triggerMock.On("List", mock.Anything, mock.Anything).Return(&v1alpha1.TriggerList{Items: []v1alpha1.Trigger{{}}}, errors.New("")).Maybe()
		templateMock.On("List", mock.Anything, mock.Anything).Return(&v1alpha1.TemplateList{Items: []v1alpha1.Template{{}}}, errors.New("")).Maybe()

		controllers.Cl = clMock

		m := GetInitManager()
		if m.DoesTriggersExist() || m.DoesScopesExist() || m.DoesTemplatesExist() {
			t.Fatal("Wrong manager initialization")
		}

		ctx, cancel := context.WithCancel(context.Background())
		go func() {
			time.Sleep(4 * time.Second)
			cancel()
		}()
		m.Start(ctx)
	})
}
